package edu.scnu.fans.fingertip.order.service;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import edu.scnu.fans.fingertip.common.api.IdRequest;
import edu.scnu.fans.fingertip.common.web.ApiResponseUtils;
import edu.scnu.fans.fingertip.common.web.BusinessException;
import edu.scnu.fans.fingertip.item.api.ItemApi;
import edu.scnu.fans.fingertip.item.output.ItemOutput;
import edu.scnu.fans.fingertip.item.output.ItemSpecOutput;
import edu.scnu.fans.fingertip.order.input.CreateOrderInput;
import edu.scnu.fans.fingertip.order.input.OrderListInput;
import edu.scnu.fans.fingertip.order.mapper.OrderItemMapper;
import edu.scnu.fans.fingertip.order.mapper.OrdersMapper;
import edu.scnu.fans.fingertip.order.model.OrderItem;
import edu.scnu.fans.fingertip.order.model.Orders;
import edu.scnu.fans.fingertip.order.output.OrderItemOutput;
import edu.scnu.fans.fingertip.order.output.OrderOutput;
import edu.scnu.fans.fingertip.user.api.UserAddressApi;
import edu.scnu.fans.fingertip.user.input.UserAddressDto;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.function.Function;
import java.util.stream.Collectors;

@Service
public class OrderService {

    @Resource
    private OrderItemMapper orderItemMapper;

    @Resource
    private OrdersMapper ordersMapper;

    @Resource
    private UserAddressApi userAddressApi;

    @Resource
    private ItemApi itemApi;

    /**
     * 创建订单
     */
    @Transactional
    public void create(Long userId, CreateOrderInput input) {
        // 微服务远程调用，获取商品详情和收货地址，如果商品或地址有误则返回异常
        ItemOutput item = ApiResponseUtils.codeOkGetData(itemApi.detail(new IdRequest(input.getItemId())));
        UserAddressDto address = ApiResponseUtils.codeOkGetData(userAddressApi.findAddressById(userId, new IdRequest(input.getAddressId())));

        Map<Long, ItemSpecOutput> specMap = item.getSpecList()
                .stream()
                .collect(Collectors.toMap(ItemSpecOutput::getId, Function.identity()));

        BigDecimal totalAmount = BigDecimal.ZERO;

        // 规格有效性校验
        for (CreateOrderInput.CreateOrderSpecInput specInput : input.getSpecList()) {
            ItemSpecOutput spec = specMap.get(specInput.getSpecId());
            if (spec == null) {
                throw new BusinessException("id = " + specInput.getSpecId() + " 的规格不存在");
            }

            // 计算总价
            totalAmount = totalAmount.add(spec.getCurrentPrice().multiply(BigDecimal.valueOf(specInput.getAmount())));
        }

        // 创建 Order
        Orders order = new Orders(userId);
        order.setReceiver(address.getReceiver());
        order.setMobile(address.getMobile());
        order.setAddress(address.getProvince() + " " + address.getCity() + " " + address.getDistrict() + " " + address.getAddressDetail());
        order.setTotalAmount(totalAmount);
        order.setRemark(input.getRemark());
        order.setOrderStatus(Orders.NOT_PAY_STATUS);

        ordersMapper.insert(order);

        // 创建 OrderItem
        for (CreateOrderInput.CreateOrderSpecInput specInput : input.getSpecList()) {
            ItemSpecOutput spec = specMap.get(specInput.getSpecId());

            OrderItem orderItem = new OrderItem(userId, order.getId(), item.getId(), specInput.getSpecId());
            orderItem.setItemTitle(item.getTitle());
            orderItem.setItemImgUrl(item.getImgList().get(0).getImgUrl());
            orderItem.setItemSpecName(spec.getName());
            orderItem.setPrice(spec.getCurrentPrice());
            orderItem.setAmount(specInput.getAmount());

            orderItemMapper.insert(orderItem);
        }
    }

    /**
     * 订单列表
     */
    public List<OrderOutput> list(Long userId, OrderListInput input) {
        LambdaQueryWrapper<Orders> query = new LambdaQueryWrapper<Orders>()
                .eq(Orders::getUserId, userId)
                .orderByDesc(Orders::getCreated);

        if (input.getOrderStatus() != null) {
            query.eq(Orders::getOrderStatus, input.getOrderStatus());
        }

        // 分页查询订单列表
        List<OrderOutput> orderList = ordersMapper.selectPage(new Page<>(input.getPageNum(), input.getPageSize()), query)
                .getRecords()
                .stream()
                .map(Orders::transferToOutput)
                .collect(Collectors.toList());

        if (CollectionUtils.isEmpty(orderList)) {
            return Collections.emptyList();
        }

        List<Long> orderIdList = orderList.stream()
                .map(OrderOutput::getId)
                .collect(Collectors.toList());

        // 查询订单商品
        Map<Long, List<OrderItemOutput>> orderItemMap = orderItemMapper.selectList(new LambdaQueryWrapper<OrderItem>()
                        .in(OrderItem::getOrderId, orderIdList))
                .stream()
                .map(OrderItem::transferToOutput)
                .collect(Collectors.groupingBy(OrderItemOutput::getOrderId));

        orderList.forEach(order -> order.setOrderItemList(orderItemMap.get(order.getId())));

        return orderList;
    }
}
